package com.mebs.model;

import org.jt.jet.annotation.ArgumentType;
import org.jt.jet.annotation.Field;
import org.jt.jet.content.JetNamedObject;
import org.jt.jet.util.JetSecurityUtils;
import org.jt.jet.util.JetUtils;

import javax.persistence.*;
import java.util.Date;
import java.util.Set;

/**
 * User: epb
 * Date: 23.10.2009
 * Time: 13:08:55
 */

@Entity()
@Inheritance(strategy = InheritanceType.JOINED)
@Table(name = "AGENT")
@PrimaryKeyJoinColumn(name = "AgentId")
public class Agent extends Occupier implements JetNamedObject {

	@Column(name = "FirstName", length = 127, nullable = false)
	private String firstName;

	@Column(name = "LastName", length = 127, nullable = false)
	private String lastName;

	@Column(name = "MiddleName", length = 127, nullable = true)
	private String middleName;

	@Column(name = "Email", length = 250, unique = true, nullable = false)
	private String email;

	@ManyToOne(optional = true)
	@JoinColumn(name = "MainAddressId")
	private Address mainAddress;

	@ManyToOne(optional = true)
	@JoinColumn(name = "WorkAddressId")
	private Address workAddress;

	@ManyToOne(optional = true)
	@JoinColumn(name = "HomeAddressId")
	private Address homeAddress;

	@Column(name = "Status", nullable = false)
	private Integer status;
	
	@Column(name = "CreationTime", nullable = false)
	private Date creationTime;

	@ManyToOne(optional = true, fetch = FetchType.LAZY)
	@JoinColumn(name = "CreatedBy")
	@Field(type = ArgumentType.INSTANCE)
	private User createdBy;

	@ManyToMany(fetch = FetchType.LAZY)
	@JoinTable(name = "AGENT_ADDRESS_CURRENT", joinColumns = {@JoinColumn(name = "AgentId")},
		inverseJoinColumns = {@JoinColumn(name = "AddressId")})
	@Field(type = ArgumentType.INSTANCE)
	private java.util.Set<Address> currentAddresses;


	/**
	 * ********************** Getters-setters ***********************
	 */
	public String getFirstName() {
		return firstName == null ? "" : firstName;
	}

	public void setFirstName(String firstName) {
		this.firstName = firstName;
	}

	public String getLastName() {
		return lastName == null ? "" : lastName;
	}

	public void setLastName(String lastName) {
		this.lastName = lastName;
	}

	public String getMiddleName() {
		return middleName == null ? "" : middleName;
	}

	public void setMiddleName(String middleName) {
		this.middleName = middleName;
	}

	public String getEmail() {
		return email;
	}

	public void setEmail(String email) {
		this.email = email;
	}

	public Integer getStatus() {
		return status;
	}

	public void setStatus(Integer status) {
		this.status = status;
	}

	public void setStatus(Agent.Status status) {
		this.status = status.status;
	}

	@Transient
	public boolean isDeleted() {
		return (this.status == Agent.Status.deleted.status);
	}

	@Transient
	public boolean isInactive() {
		return (this.status == Agent.Status.inactive.status);
	}

	public Address getMainAddress() {
		return mainAddress;
	}

	public void setMainAddress(Address mainAddress) {
		this.mainAddress = mainAddress;
	}

	public Address getWorkAddress() {
		return workAddress;
	}

	public void setWorkAddress(Address workAddress) {
		this.workAddress = workAddress;
	}

	@Transient
	public boolean hasWorkAddress(Address workAddress) {
		return this.workAddress != null &&
				workAddress != null &&
				this.workAddress.equals(workAddress);
	}

	public Address getHomeAddress() {
		return homeAddress;
	}

	public void setHomeAddress(Address homeAddress) {
		this.homeAddress = homeAddress;
	}

	@Transient
	public boolean hasHomeAddress(Address homeAddress) {
		return this.homeAddress != null &&
				homeAddress != null &&
				this.homeAddress.equals(homeAddress);
	}

	public Date getCreationTime() {
		return creationTime;
	}

	public void setCreationTime(Date creationTime) {
		this.creationTime = creationTime;
	}

	public User getCreatedBy() {
		return createdBy;
	}

	public void setCreatedBy(User createdBy) {
		this.createdBy = createdBy;
	}

	
	public Set<Address> getCurrentAddresses() {
		return currentAddresses;
	}

	public void setCurrentAddresses(Set<Address> currentAddresses) {
		this.currentAddresses = currentAddresses;
	}

	@Transient
	public boolean hasCurrentAddress(Address address) {
		return this.currentAddresses != null &&
				address != null &&
				this.currentAddresses.contains(address);
	}

	@Transient()
	public String getFullName() {
		String fullName = "";

		if (!JetUtils.isEmpty(firstName)) {
			fullName = firstName;
		}
		if (!JetUtils.isEmpty(middleName)) {
			if (!fullName.equals("")) {
				fullName = fullName.concat(" ");
			}
			fullName = fullName.concat(middleName);
		}
		if (!JetUtils.isEmpty(lastName)) {
			if (!fullName.equals("")) {
				fullName = fullName.concat(" ");
			}
			fullName = fullName.concat(lastName);
		}

		return fullName;
	}

	////////////////////////////////////////////////////
	// JetUser overrides
	////////////////////////////////////////////////////

	@Transient
	public String getStatusString() {
		return status == null ? "" : Status.getByStatus(status).getObjectName();
	}

	////////////////////////////////////////////////////
	// JetNamedObject overrides
	////////////////////////////////////////////////////

	@Transient()
	public Object getObjectId() {
		return getId();
	}

	@Transient()
	public String getObjectName() {
		return getFullName();
	}

	public enum Status implements JetNamedObject {
		active(1),
		inactive(2),
		deleted(3);

		public final int status;

		Status(int status) {
			this.status = status;
		}

		public Object getObjectId() {
			return status;
		}

		public String getObjectName() {
			return name();
		}

		public int getStatus() {
			return status;
		}

		public static Status getByStatus(int id) {
			for (Status status : Status.values()) {
				if (status.getStatus() == id) {
					return status;
				}
			}
			return null;
		}
	}

	@Override
	public String toString() {
		return this.getFullName();
	}


}
